package com.sos.core.game
{
	import com.sos.core.Stats;
	
	import flash.events.Event;
	
	public class GameStats extends Stats
	{
				
		// -------------------------------------------------------------------------------
		// CONSTANTS
		// -------------------------------------------------------------------------------

		// JSON data properties names
		public static const 	JSON_PROPERTY_YELLOW_CARDS:String		= "yellowCards";
		public static const 	JSON_PROPERTY_RED_CARDS:String			= "redCards";
		
		// Default values
		private static const 	DEFAULT_YELLOW_CARDS:int				= 0;
		private static const 	DEFAULT_RED_CARDS:int					= 0;
		
		// Events
		public static const     EVENT_GAME_STATS_CHANGED:String			= "game_stats_changed";
		
		// -------------------------------------------------------------------------------
		// FIELDS
		// -------------------------------------------------------------------------------
		
		protected var _yellowCards:uint;
		protected var _redCards:uint;
		
		// -------------------------------------------------------------------------------
		// CONSTRUCTOR
		// -------------------------------------------------------------------------------		
		
		public function GameStats()
		{
			// Call ancestor
			super();
			// Clears data
			clear();
		}		
		
		// -------------------------------------------------------------------------------
		// PROPERTIES
		// -------------------------------------------------------------------------------
		
		public function get isExpelled():Boolean
		{
			return _redCards > 0;
		}
		
		public function get canPlay():Boolean
		{
			return _stamina > 0;
		}
		
		[Bindable(event="game_stats_changed")]
		public function get yellowCards():uint
		{
			return _yellowCards;
		}
		
		public function set yellowCards(value:uint):void
		{
			_yellowCards = value;
		}
		
		[Bindable(event="game_stats_changed")]
		public function get redCards():uint
		{
			return _redCards;
		}
		
		public function set redCards(value:uint):void
		{
			_redCards = value;
		}		
		
		// -------------------------------------------------------------------------------
		// PRIVATE METHODS
		// -------------------------------------------------------------------------------
		
		// Stats methods redefinition
		
		// LT_TODO:fare un metodo che prende le stats base e i le game stats risultato dei mod e aggiorna le stats correnti
		
		// DataObject implementation
		
		override protected function validate(data:Object):void
		{
			super.validate(data);
			// JSON properties check
			if (!data.hasOwnProperty(JSON_PROPERTY_YELLOW_CARDS))	throwLoadMissingPropError("yellow cards");
			if (!data.hasOwnProperty(JSON_PROPERTY_RED_CARDS)) 		throwLoadMissingPropError("red cards");
		}
		
		override protected function fill(data:Object):void
		{
			// Ancestor call
			super.fill(data);
			// 
			_yellowCards = uint(data[JSON_PROPERTY_YELLOW_CARDS]);
			_redCards 	 = uint(data[JSON_PROPERTY_RED_CARDS]);
			// Dispatch event EVENT_STATS_CHANGED
			dispatchGameStatsChanged();
		}
		
		// Events dispatcher
		
		protected function dispatchGameStatsChanged():void
		{
			dispatchEvent(new Event(EVENT_GAME_STATS_CHANGED));
		}
		
		// -------------------------------------------------------------------------------
		// PUBLIC METHODS
		// -------------------------------------------------------------------------------

		/**
		 * Recalculates the status, merging the base stats and the total modifiers contained
		 * into the 'mod' GameStats perameter
		 * @param stats Base stats (fixed)
		 * @param mod Total stats modifiers to apply to the base stats
		 */		
		public function set(stats:Stats, mod:GameStats):void
		{
			// 
			var temp:GameStats = new GameStats();
			// Copy the base stats
			temp.copy(stats);
			// Update stats with the mods totals
			temp.update(mod);
			// Copy in the current status
			copy(temp);
		}
		
		override public function update(stats:Stats):void
		{
			// Check stats type
			if (stats is GameStats)
			{
				// Merges the current stats with the provided one
				var merge:GameStats = merge(stats) as GameStats;
				// Copies data from the merged object
				copy(merge);
			}
			else
			{
				super.update(stats);
			}
		}
		
		override public function merge(stats:Stats):Stats
		{
			// Check stats type
			if (stats is GameStats)
			{
				// Cast Stats to GameStats
				var gameStats:GameStats = stats as GameStats;
				// Create the new object
				var delta:GameStats = new GameStats();
				// Stats merge
				delta.stamina 		= _stamina		+ stats.stamina;
				delta.dribiling 	= _dribiling	+ stats.dribiling;
				delta.passing 		= _passing		+ stats.passing;
				delta.scoring 		= _scoring		+ stats.scoring;
				delta.defence 		= _defence		+ stats.defence;
				delta.goalkeeping	= _goalkeeping	+ stats.goalkeeping;
				// Cars values are not merged but copied
				delta.yellowCards = gameStats.yellowCards;
				delta.redCards 	  = gameStats.redCards;
				// Returns the new object
				return delta;
			}
			else
			{
				return super.merge(stats);
			}
		}
		
		override public function copy(stats:Stats):void
		{
			if (stats is GameStats)
			{
				// Cast to game stats
				var gameStats:GameStats = stats as GameStats;
				// Check if data is different from the current 
				if (!equals(gameStats))
				{
					// Ancestor copy
					super.copy(stats);
					// Copy data
					_yellowCards 	= gameStats.yellowCards; 
					_redCards		= gameStats.redCards;
					// Dispatch event EVENT_GAME_STATS_CHANGED
					dispatchGameStatsChanged();
				}
			}
			else
			{
				super.copy(stats);
			}
		}
		
		override public function clone():Stats
		{
			var stats:GameStats = new GameStats();
			stats.copy(this);
			return stats;
		}
		
		override public function clear():void
		{
			// Ancestor clear
			super.clear();
			// Clear data
			_yellowCards 	= DEFAULT_YELLOW_CARDS; 
			_redCards		= DEFAULT_RED_CARDS;
			// Dispatch event EVENT_GAME_STATS_CHANGED
			dispatchGameStatsChanged();
		}

	}
}